﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace KeywordAuction
{
    public class AuctionHost: ICloneable
    {
        public List<Adspot> Adspots { get; set; }
        public List<Advertiser> Advertisers { get; set; }

        public int Round { get; set; }

        public IAuctionMechanism AuctionMechanism { get; set; }
        public AuctionHost()
        {
            Adspots = new List<Adspot>();
            Advertisers = new List<Advertiser>();
        }

        public void GoNextRound()
        {
            var strategies = Advertisers.Select(p =>new Tuple<Advertiser,IStrategy>(p,  p.Tactics.GetStrategy(p)));
            foreach (var item in strategies)
            {
                item.Item2.Action(item.Item1);
            }
        }

        public Adspot CreateAdspot()
        {
            var adspot = new Adspot();
            adspot.AuctionHost = this;
            return adspot;
        }
        public Advertiser CreateAdvertiser()
        {
            var advertiser = new Advertiser();
            advertiser.AttendingAuction = this;
            return advertiser;
        }

        public object Clone()
        {
            var auctionHost = new SimulationAuctionHost();
            auctionHost.ParentAuctionHost = null;
            auctionHost.AuctionMechanism= this.AuctionMechanism;
            //this.ChildAuctionHost.Add(auctionHost);

            foreach (var item in Adspots)
            {
                var adspot = auctionHost.CreateAdspot();
                adspot.ClickThroughtRates = item.ClickThroughtRates.ToList();
                adspot.Traffic = item.Traffic;
                adspot.Id= item.Id;

                auctionHost.Adspots.Add(adspot);
            }
            foreach (var item in this.Advertisers)
            {
                var advertiser = new Advertiser();
                advertiser.Strategies = item.Strategies.ToList();
                advertiser.BudgetConstraint = item.BudgetConstraint;
                advertiser.Tactics = item.Tactics;
                advertiser.AttendingAuction = this;
                advertiser.CurrentStrategy = item.CurrentStrategy;
                advertiser.Id = item.Id;
                foreach (var bid in item.Biddings)
                {
                    var adspot = auctionHost.Adspots.Where(p => bid.AttendingAdspot.Id == p.Id).FirstOrDefault();
                    var newBid = AdvertiserBidding.CreateAdvertiserBidding(advertiser, adspot);
                    newBid.ExpectedRevenue = bid.ExpectedRevenue;
                    newBid.Bid = bid.Bid;
                    adspot.Bitting.Add(newBid);
                    advertiser.Biddings.Add(newBid);
                }
                auctionHost.Advertisers.Add(advertiser);
            }
            return auctionHost;
        }
        public string Name { get; set; }
    }
}
